#include "../ui.h"
#include "../../client/net_client.h"
#include "../../protocol/protocol.h"
#include "../../online_user/online_user.h"
#include <string.h>
#include <stdio.h>
#include <pthread.h>
#include <ctype.h>

// 核心LVGL头文件
#include "lvgl/src/core/lv_obj.h"
#include "lvgl/src/extra/widgets/list/lv_list.h"

// 函数原型声明
void ui_refresh_user_list(void);
void ui_add_chat_log(const char * sender, const char * message);
void ui_handle_receive_msg(uint32_t sender_id, const char * nickname, const char * msg);
static void handle_online_list(const char * data);
static void free_online_users(void);
static lv_obj_t * my_lv_obj_get_next_siblin(lv_obj_t * obj);
// 全局UI组件
lv_obj_t * ui_Screen3;
lv_obj_t * ui_user_list;   // Online user list
lv_obj_t * ui_chat_log;    // Chat history display
lv_obj_t * ui_chat_input;  // Message input box
lv_obj_t * ui_send_btn;    // Send button
lv_obj_t * ui_keyboard;    // Virtual keyboard
lv_obj_t * ui_title_label; // Title label

// 数据管理与线程控制
OnlineUserList g_screen3_online_users = {0};
pthread_mutex_t g_user_mutex          = PTHREAD_MUTEX_INITIALIZER;
static uint32_t g_selected_user_id    = 0; 
static char* get_selected_user_nickname;
static pthread_t g_receive_thread;         
static bool g_receive_running = false;

// 手动实现“获取下一个兄弟对象”的兼容函数,lvgl8.2没有这个函数
static lv_obj_t * my_lv_obj_get_next_siblin(lv_obj_t * obj)
{
    if(!obj || !lv_obj_get_parent(obj)) {
        return NULL; // 无父容器，无兄弟对象
    }
    // 1. 获取当前对象在父容器中的索引
    uint32_t current_idx = lv_obj_get_index(obj);
    // 2. 获取父容器的子对象总数
    uint32_t child_count = lv_obj_get_child_cnt(lv_obj_get_parent(obj));
    // 3. 索引+1，获取下一个子对象
    if(current_idx + 1 < child_count) {
        return lv_obj_get_child(lv_obj_get_parent(obj), current_idx + 1);
    } else {
        return NULL; // 已是最后一个子对象
    }
}

static char * str_trim(char * str)
{
    if(!str) return NULL;
    while(*str && isspace((unsigned char)*str)) str++;
    if(*str) {
        char * end = str + strlen(str) - 1;
        while(end > str && isspace((unsigned char)*end)) end--;
        *(end + 1) = '\0';
    }
    return str;
}

// User list item click event
static void ui_event_user_list_item(lv_event_t * e)
{
    lv_obj_t * item    = lv_event_get_target(e);
    g_selected_user_id = (uint32_t)(uintptr_t)lv_obj_get_user_data(item);

    // Update selection style
    lv_obj_t * list  = lv_obj_get_parent(item);
    lv_obj_t * child = lv_obj_get_child(list, 0);
    while(child) {
        if(child == item) {
            lv_obj_set_style_bg_color(child, lv_color_hex(0x0078D7), LV_PART_MAIN);
            lv_obj_set_style_text_color(child, lv_color_hex(0xFFFFFF), LV_PART_MAIN);
            lv_obj_set_style_pad_all(child, 8, LV_PART_MAIN);
        } else {
            lv_obj_set_style_bg_color(child, lv_color_hex(0xFFFFFF), LV_PART_MAIN);
            lv_obj_set_style_text_color(child, lv_color_hex(0x333333), LV_PART_MAIN);
            lv_obj_set_style_pad_all(child, 6, LV_PART_MAIN);
        }
        child = my_lv_obj_get_next_siblin(child);
    }

    // Log selected user
    printf("[Screen3] Selected user ID: %d, Nickname: %s\n", g_selected_user_id,
           lv_list_get_btn_text(ui_user_list, item));
}

// Refresh online user list
void ui_refresh_user_list(void)
{
    if(!ui_user_list) return;

    // Clear existing list
    lv_obj_clean(ui_user_list);

    pthread_mutex_lock(&g_user_mutex);
    // Add all online users
    for(uint32_t i = 0; i < g_screen3_online_users.count; i++) {
        lv_obj_t * item = lv_list_add_btn(ui_user_list, NULL, g_screen3_online_users.users[i].nickname);
        lv_obj_set_user_data(item, (void *)(uintptr_t)g_screen3_online_users.users[i].user_id);
        lv_obj_add_event_cb(item, ui_event_user_list_item, LV_EVENT_CLICKED, NULL);

        // Restore selection state
        if(g_selected_user_id == g_screen3_online_users.users[i].user_id) {
            lv_obj_set_style_bg_color(item, lv_color_hex(0x0078D7), LV_PART_MAIN);
            lv_obj_set_style_text_color(item, lv_color_hex(0xFFFFFF), LV_PART_MAIN);
            lv_obj_set_style_pad_all(item, 8, LV_PART_MAIN);
        } else {
            lv_obj_set_style_text_color(item, lv_color_hex(0x333333), LV_PART_MAIN);
        }
    }
    pthread_mutex_unlock(&g_user_mutex);
}

// Add message to chat log
void ui_add_chat_log(const char * sender, const char * message)
{
    if(!ui_chat_log) return;

    char log_text[512];
    snprintf(log_text, sizeof(log_text), "[%s]: %s\n", sender, message);
    lv_label_ins_text(ui_chat_log, LV_LABEL_POS_LAST, log_text);

    // Auto scroll to bottom
    lv_obj_scroll_to_view(ui_chat_log, LV_ANIM_ON);
}

// Screen click event (hide keyboard)
static void ui_event_screen_click(lv_event_t * e)
{
    lv_obj_t * target = lv_event_get_target(e);
    if(target != ui_chat_input && target != ui_keyboard) {
        lv_obj_add_flag(ui_keyboard, LV_OBJ_FLAG_HIDDEN);
        lv_obj_clear_state(ui_chat_input, LV_STATE_FOCUSED);
    }
}

// Input box event (control keyboard)
static void ui_event_chat_input(lv_event_t * e)
{
    lv_event_code_t code = lv_event_get_code(e);

    if(code == LV_EVENT_CLICKED || code == LV_EVENT_FOCUSED) {
        lv_keyboard_set_textarea(ui_keyboard, ui_chat_input);
        lv_obj_clear_flag(ui_keyboard, LV_OBJ_FLAG_HIDDEN);
    } else if(code == LV_EVENT_DEFOCUSED) {
        lv_obj_add_flag(ui_keyboard, LV_OBJ_FLAG_HIDDEN);
    } else if(code == LV_EVENT_KEY) {
        uint32_t key = *(uint32_t *)lv_event_get_param(e);
        if(key == LV_KEY_ENTER) {
            lv_event_send(ui_send_btn, LV_EVENT_CLICKED, NULL);
        }
    }
}

// 发送数据
static void ui_event_send_btn(lv_event_t * e)
{
    if(lv_event_get_code(e) != LV_EVENT_CLICKED) return;

    const char * input = lv_textarea_get_text(ui_chat_input);
    if(!input || strlen(input) == 0) return;

    char * text = strdup(input);
    if(!text) return;
    str_trim(text);

    if(strlen(text) > 0) {
        if(g_selected_user_id == 0) {
            ui_add_chat_log("System", "Please select a user from the left list first");
        } else {
            net_send_private_msg(g_selected_user_id, text);
            ui_add_chat_log("Me", text);
            lv_textarea_set_text(ui_chat_input, "");
        }
    }

    free(text);
    lv_obj_add_flag(ui_keyboard, LV_OBJ_FLAG_HIDDEN);
}

void ui_handle_receive_msg(uint32_t sender_id, const char * nickname, const char * msg)
{
    if(!nickname || !msg || !ui_chat_log) return;

    ui_add_chat_log(nickname, msg);

    if(sender_id != g_selected_user_id) {
        pthread_mutex_lock(&g_user_mutex);
        for(uint32_t i = 0; i < g_screen3_online_users.count; i++) {
            if(g_screen3_online_users.users[i].user_id == sender_id) {
                ui_refresh_user_list();
                break;
            }
        }
        pthread_mutex_unlock(&g_user_mutex);
    }
}

// 处理服务器端的数据
static void * receive_server_data(void * arg)
{
    int * sockfd = (int *)arg;
    printf("[Screen3] 开始接收服务器数据线程: %d\n", *sockfd);

    char recv_buf[1024];
    while(g_receive_running && *sockfd != -1) {
        ssize_t len = recv(*sockfd, recv_buf, sizeof(recv_buf) - 1, 0);
        if(len <= 0) {
            if(len < 0)
                perror("[Screen3] 接收数据错误");
            else
                printf("[Screen3] 服务器断开连接\n");
            break;
        }
        recv_buf[len] = '\0';
        printf("[Screen3] 收到数据长度: %zd, 内容: %s\n", len, recv_buf);

        char * type_str = strtok(recv_buf, ":");
        if(!type_str) continue;

        int msg_type = atoi(type_str);
        char * data  = strtok(NULL, "");

        switch(msg_type) {
            case 10:
                printf("[Screen3] 收到的数据类型: 10\n");
                handle_online_list(data);
                break;
            case 30:
                printf("[Screen3] 收到的数据类型: 20\n");
                if(data) {
                    char * sender_id_str = strtok(data, ":");
                    char * nickname      = strtok(NULL, ":");
                    char * msg           = strtok(NULL, "");
                    if(sender_id_str && nickname && msg) {
                        ui_handle_receive_msg(atoi(sender_id_str), nickname, msg);
                    }
                }
                break;
            default: printf("[Screen3] Unknown message type: %d\n", msg_type);
        }
    }

    printf("[Screen3] Receive thread exited\n");
    g_receive_running = false;
    return NULL;
}

// Refresh event handler
static void ui_Screen3_refresh_event(lv_event_t * e)
{
    if(lv_event_get_code(e) == LV_EVENT_REFRESH) {
        printf("[Screen3] UI refresh event triggered\n");
        ui_refresh_user_list();
    }
}

// 处理在线用户的链表
static void handle_online_list(const char * data)
{
    printf("[Screen3] Processing online list update, data: %s\n", data ? data : "null");
    OnlineUserList new_list = {0};

    if(protocol_parse_online_list(data, &new_list)) {

        printf("[Screen3] Parsing successful, new_list contains %d users:\n", new_list.count);
        for(uint32_t i = 0; i < new_list.count; i++) {
            printf("[Screen3] User%d: ID=%d, Nickname=%s\n", i, new_list.users[i].user_id,
                   new_list.users[i].nickname ? new_list.users[i].nickname : "null");
        }

        pthread_mutex_lock(&g_user_mutex);
        free_online_users();
        g_screen3_online_users = new_list;
        pthread_mutex_unlock(&g_user_mutex);

        printf("[Screen3] Online list updated, current user count: %d\n", g_screen3_online_users.count);

        // Trigger UI refresh
        lv_event_send(ui_Screen3, LV_EVENT_REFRESH, NULL);
        printf("[Screen3] UI refresh event sent\n");
    } else {
        printf("[Screen3] Online list parsing failed\n");
        // Free partially allocated memory
        for(uint32_t i = 0; i < new_list.count; i++) {
            free((void *)new_list.users[i].nickname);
        }
        free(new_list.users);
    }
}

// Free online user list memory
static void free_online_users(void)
{
    if(g_screen3_online_users.users) {
        for(uint32_t i = 0; i < g_screen3_online_users.count; i++) {
            free((void *)g_screen3_online_users.users[i].nickname);
            g_screen3_online_users.users[i].nickname = NULL;
        }
        free(g_screen3_online_users.users);
        g_screen3_online_users.users = NULL;
    }
    g_screen3_online_users.count = 0;
}

// Initialize UI layout
static void ui_Screen3_create_layout(void)
{
    // Main screen
    ui_Screen3 = lv_obj_create(NULL);
    lv_obj_clear_flag(ui_Screen3, LV_OBJ_FLAG_SCROLLABLE);
    lv_obj_set_style_bg_color(ui_Screen3, lv_color_hex(0xFFFFFF), LV_PART_MAIN);
    lv_obj_add_event_cb(ui_Screen3, ui_event_screen_click, LV_EVENT_CLICKED, NULL);

    // Title label (use LVGL default font)
    ui_title_label = lv_label_create(ui_Screen3);
    lv_label_set_text(ui_title_label, "Online Chat");
    // Remove custom font binding, use LVGL default font
    lv_obj_align(ui_title_label, LV_ALIGN_TOP_MID, 0, 10);

    // Left user list
    uint32_t user_list_width = LV_HOR_RES / 3;
    if(user_list_width > 300)
        user_list_width = 300;
    else if(user_list_width < 150)
        user_list_width = 150;
    ui_user_list = lv_list_create(ui_Screen3);
    lv_obj_set_size(ui_user_list, user_list_width, LV_VER_RES - 20);
    lv_obj_align(ui_user_list, LV_ALIGN_LEFT_MID, 10, 0);
    lv_obj_set_style_bg_color(ui_user_list, lv_color_hex(0xF5F5F5), LV_PART_MAIN);
    lv_obj_set_style_radius(ui_user_list, 8, LV_PART_MAIN);
    lv_obj_set_style_shadow_width(ui_user_list, 2, LV_PART_MAIN);
    lv_obj_set_style_shadow_color(ui_user_list, lv_color_hex(0xDDDDDD), LV_PART_MAIN);

    // Right chat area
    uint32_t chat_area_width = LV_HOR_RES - user_list_width - 40;

    // Chat log display
    ui_chat_log = lv_label_create(ui_Screen3);
    lv_obj_set_size(ui_chat_log, chat_area_width, LV_VER_RES - 120);
    lv_obj_align(ui_chat_log, LV_ALIGN_TOP_RIGHT, -20, 40);
    lv_label_set_long_mode(ui_chat_log, LV_LABEL_LONG_WRAP);
    lv_obj_set_style_bg_color(ui_chat_log, lv_color_hex(0xFAFAFA), LV_PART_MAIN);
    lv_obj_set_style_border_width(ui_chat_log, 1, LV_PART_MAIN);
    lv_obj_set_style_radius(ui_chat_log, 8, LV_PART_MAIN);
    lv_obj_set_style_pad_all(ui_chat_log, 10, LV_PART_MAIN);
    lv_label_set_text(ui_chat_log, "System: Please select a user from the left list to start chatting\n");

    // Message input box
    ui_chat_input = lv_textarea_create(ui_Screen3);
    lv_obj_set_size(ui_chat_input, chat_area_width - 100, 50);
    lv_obj_align(ui_chat_input, LV_ALIGN_BOTTOM_RIGHT, -110, -60);
    lv_textarea_set_placeholder_text(ui_chat_input, "Type a message...");
    lv_obj_add_event_cb(ui_chat_input, ui_event_chat_input, LV_EVENT_ALL, NULL);
    lv_obj_set_style_radius(ui_chat_input, 6, LV_PART_MAIN);

    // Send button
    ui_send_btn = lv_btn_create(ui_Screen3);
    lv_obj_set_size(ui_send_btn, 80, 50);
    lv_obj_align_to(ui_send_btn, ui_chat_input, LV_ALIGN_OUT_RIGHT_MID, 10, 0);
    lv_obj_add_event_cb(ui_send_btn, ui_event_send_btn, LV_EVENT_CLICKED, NULL);
    lv_obj_set_style_radius(ui_send_btn, 25, LV_PART_MAIN);
    lv_obj_set_style_bg_color(ui_send_btn, lv_color_hex(0x0078D7), LV_PART_MAIN);
    lv_obj_set_style_bg_color(ui_send_btn, lv_color_hex(0x005A9E), LV_PART_MAIN | LV_STATE_PRESSED);

    lv_obj_t * send_label = lv_label_create(ui_send_btn);
    lv_label_set_text(send_label, "Send");
    lv_obj_set_style_text_color(send_label, lv_color_hex(0xFFFFFF), LV_PART_MAIN);
    lv_obj_center(send_label);

    // Virtual keyboard (hidden by default)
    ui_keyboard = lv_keyboard_create(ui_Screen3);
    lv_obj_set_width(ui_keyboard, LV_HOR_RES);
    lv_obj_set_height(ui_keyboard, 200);
    lv_obj_align(ui_keyboard, LV_ALIGN_BOTTOM_MID, 0, 0);
    lv_obj_add_flag(ui_keyboard, LV_OBJ_FLAG_HIDDEN);
}

// Initialize screen
void ui_Screen3_screen_init(void)
{
    ui_Screen3_create_layout();

    // Start receive thread
    extern int g_sockfd;
    if(g_sockfd != -1) {
        g_receive_running = true;
        int ret           = pthread_create(&g_receive_thread, NULL, receive_server_data, &g_sockfd);
        if(ret != 0) {
            printf("[Screen3] Failed to create receive thread, error: %d\n", ret);
            g_receive_running = false;
        } else {
            pthread_detach(g_receive_thread);
            printf("[Screen3] Receive thread created and detached\n");
        }
    } else {
        printf("[Screen3] Invalid socket (%d), receive thread not started\n", g_sockfd);
    }

    // Add refresh event
    lv_obj_add_event_cb(ui_Screen3, ui_Screen3_refresh_event, LV_EVENT_REFRESH, NULL);
    printf("[Screen3] Screen initialized\n");
}

// Destroy screen
void ui_Screen3_screen_destroy(void)
{
    // Stop receive thread
    g_receive_running = false;

    if(ui_Screen3) {
        lv_obj_del(ui_Screen3);
        ui_Screen3 = NULL;
    }

    // Free user list resources
    pthread_mutex_lock(&g_user_mutex);
    free_online_users();
    pthread_mutex_unlock(&g_user_mutex);

    pthread_mutex_destroy(&g_user_mutex);
    printf("[Screen3] Screen destroyed\n");
}
